﻿using System.Linq;
using System.Web.Mvc;
using System.Web.UI.WebControls;
using Mvc.XForms.Examples.Model;
using Mvc.XForms.Examples.Repository;
using Mvc.XForms.Examples.Validation;
using Mvc.XForms.UI;

namespace Mvc.XForms.Examples.Controllers {
	[HandleError]
	public class CustomerController : Controller {
		private readonly IRepository<Customer> customerRepository;
		private readonly IRepository<Planet> planetRepository;
		private readonly IRepository<MailingList> mailingListRepository;

		public CustomerController(IRepository<Customer> customerRepository, IRepository<Planet> planetRepository, IRepository<MailingList> mailingListRepository) {
			this.customerRepository = customerRepository;
			this.planetRepository = planetRepository;
			this.mailingListRepository = mailingListRepository;
		}

		public ActionResult List() {
			var gridParams = new PagedSortedParameters<Customer>(Request.QueryString, "p", "sort", "dir", 2, c => c.Name, SortDirection.Ascending);
			var customerPaged = new LinqPagedSortedList<Customer>(customerRepository.AsQueryable(), gridParams);
			return View(customerPaged);
		}

		[AcceptVerbs("GET")]
		public ActionResult Add() {
			var viewData = new CustomerViewData {
				Customer = new Customer(),
				Planets = planetRepository.AsQueryable().ToList(),
				MailingLists = mailingListRepository.AsQueryable().ToList(),
				IsEditing = false
			};

			return View("Details", viewData);
		}

		[AcceptVerbs("POST")]
		public ActionResult Add(FormCollection form) {
			// Deserialize new customer
			var customer = new Customer();
			var ds = new ExampleDeserializer(ViewData.ModelState);
			ds.Deserialize(customer, form);

			// Validate
			var validator = new CustomerValidator(customer, ViewData.ModelState, customerRepository);

			if (validator.Validate()) {
				customerRepository.Add(customer);
				return RedirectToAction("Edit", new { id = customer.ID });
			} else {
				var viewData = new CustomerViewData {
					Customer = customer,
					Planets = planetRepository.AsQueryable().ToList(),
					MailingLists = mailingListRepository.AsQueryable().ToList(),
					IsEditing = false,
				};

				return View("Details", viewData);
			}
		}

		[AcceptVerbs("GET")]
		public ActionResult Edit(long id) {
			var viewData = new CustomerViewData {
				Customer = customerRepository.Get(id),
				Planets = planetRepository.AsQueryable().ToList(),
				MailingLists = mailingListRepository.AsQueryable().ToList(),
				IsEditing = true
			};

			return View("Details", viewData);
		}

		[AcceptVerbs("POST")]
		public ActionResult Edit(long id, FormCollection form) {
			// Deserialize customer
			var ds = new ExampleDeserializer(ViewData.ModelState);
			var customer = customerRepository.Get(id);
			ds.Deserialize(customer, form);

			// Validate
			var validator = new CustomerValidator(customer, ViewData.ModelState, customerRepository);

			if (validator.Validate()) {
				customerRepository.Update(customer);
				return RedirectToAction("List");
			} else {
				var viewData = new CustomerViewData {
					Customer = customer,
					Planets = planetRepository.AsQueryable().ToList(),
					MailingLists = mailingListRepository.AsQueryable().ToList(),
					IsEditing = true
				};

				return View("Details", viewData);
			}
		}
	}
}